DefaultDrawingsSnapshotsRepo
- Stores snapshots (undo and redo steps) of drawings as scripts. A snapshot is saved when changing the color of a drawing, moving its point, changing the line width, or changing the font size.
- Snapshots are parsed and placed in the
com.devexperts.dxcharts.lib.domain.drawings.AllDrawingsSnapshot
class. - The repository includes methods for:
- adding a new snapshot -
addSnapshot
- checking for the existence of a previous snapshot -
hasPreviousStep
- checking for the existence of a next snapshot -
hasNextStep
- going to the previous snapshot -
previousStep
- going to the next snapshot -
nextStep
- checking for the presence of at least one snapshot -
canClear
- returning the current version of the set snapshot -
currentVersion
- adding a new snapshot -
Default implementation of the repository:
/*** Default implementation of [DrawingsSnapshotsRepo].** This class provides a default implementation of the [DrawingsSnapshotsRepo] interface.** @property snapshots List of all drawing snapshots.* @property getMaxVersion Callback function to get the maximum snapshot index.* @property setMaxVersion Callback function to set the maximum snapshot index.* @property getCurrentVersionCallback Callback function to get the current snapshot index.* @property incrementAndGetCurrentVersion Callback function to increment and get the current snapshot index.* @property decrementAndGetCurrentVersion Callback function to decrement and get the current snapshot index.*/open class DefaultDrawingsSnapshotsRepo(private val snapshots: MutableList<AllDrawingsSnapshot>,@get:Synchronized private val getMaxVersion: () -> Int,@get:Synchronized private val setMaxVersion: (Int) -> Unit,@get:Synchronized private val getCurrentVersionCallback: () -> Int,@get:Synchronized private val incrementAndGetCurrentVersion: () -> Int,@get:Synchronized private val decrementAndGetCurrentVersion: () -> Int,) : DrawingsSnapshotsRepo {/*** Initializes the repository with an empty snapshot.*/init {snapshots.add(0, AllDrawingsSnapshot.Empty)}/*** Method to add a new snapshot.** When adding a new snapshot [snapshot], if it differs from the last emitted:* - the drawing is added to the [snapshots] list,* - the current version variable is incremented,* - the maximum version variable is set to the current version.** Accordingly, if a snapshot with index 3 was set, with a maximum version of 7, then when adding a new snapshot versions 4, 5, 6, 7 will be erased,* and a new snapshot with version 4 is recorded instead, current = 4, max = 4.** @param snapshot The snapshot to add.*/@Synchronizedoverride fun addSnapshot(snapshot: AllDrawingsSnapshot) {val newList = snapshot.drawingsListval oldList = snapshots[getCurrentVersionCallback()].drawingsListif (!newList.cmp(oldList)) {snapshots.add(incrementAndGetCurrentVersion(), snapshot)setMaxVersion(getCurrentVersionCallback())}}/*** Returns true if the version of the snapshot is not equal to 0 - it is possible to go back to the previous snapshot, otherwise false.** @return True if the previous step is available, otherwise false.*/@Synchronizedoverride fun hasPreviousStep(): Boolean {return getCurrentVersionCallback() != 0}/*** Returns true if the version of the snapshot is not equal to the maximum - it is possible to move to the next snapshot, otherwise false.** @return True if the next step is available, otherwise false.*/@Synchronizedoverride fun hasNextStep(): Boolean {return getCurrentVersionCallback() != getMaxVersion()}/*** Returns true if the current snapshot is not empty - it is possible to clear all drawings, otherwise false.** @return True if clear is possible, otherwise false.*/@Synchronizedoverride fun canClear(): Boolean {return snapshots[getCurrentVersionCallback()] != AllDrawingsSnapshot.Empty}/*** Sets the previous snapshot as the current one and returns it.** If the current snapshot is the first one, returns null.** @return Previous snapshot or null.*/@Synchronizedoverride fun previousStep(): AllDrawingsSnapshot? {return if (getCurrentVersionCallback() != 0) {snapshots[decrementAndGetCurrentVersion()]} else {null}}/*** Sets the next snapshot as the current one and returns it.** If the current snapshot is the last one, returns null.** @return Next snapshot or null.*/@Synchronizedoverride fun nextStep(): AllDrawingsSnapshot? {return if (getCurrentVersionCallback() != getMaxVersion()) {snapshots[incrementAndGetCurrentVersion()]} else {null}}/*** Returns the version of the current snapshot.** @return The version of the current snapshot.*/@Synchronizedoverride fun currentVersion(): Int {return getCurrentVersionCallback()}}/*** Method for comparing two lists of drawings based on properties:* - id,* - keyPoints,* - type,* - properties.line.lineWidth,* - properties.text.textSize,* - properties.line.lineColor,* - properties.background.fillStyle,* - properties.text.textBg,* - properties.textValue* as well as their size.** @return True if the lists are equal, otherwise false.*/private fun DrawingsList.cmp(other: DrawingsList): Boolean {val list1 = this.listval list2 = other.listif (list1 == null || list2 == null) {return list1 == null && list2 == null}if (list1.size != list2.size) {return false}list1.forEachIndexed { index, drawingObject ->val equals = (drawingObject.id == list2[index].id&& drawingObject.keyPoints == list2[index].keyPoints&& drawingObject.type == list2[index].type&& drawingObject.properties?.line?.lineWidth == list2[index].properties?.line?.lineWidth&& drawingObject.properties?.text?.textSize == list2[index].properties?.text?.textSize&& drawingObject.properties?.line?.lineColor == list2[index].properties?.line?.lineColor&& drawingObject.properties?.background?.fillStyle == list2[index].properties?.background?.fillStyle&& drawingObject.properties?.text?.textBg == list2[index].properties?.text?.textBg&& drawingObject.properties?.textValue == list2[index].properties?.textValue)if (!equals) {return false}}return true}
Implementation of the default repository for local storage:
/*** Local storage implementation of [DrawingsSnapshotsRepo].** This class provides a local storage implementation of the [DrawingsSnapshotsRepo] interface,* storing drawing snapshots locally with support for navigation and clearing.** @constructor Creates a LocalStorageDefaultDrawingsSnapshotsRepo.*/class LocalStorageDefaultDrawingsSnapshotsRepo : DrawingsSnapshotsRepo {/*** The maximum snapshot version.*/private var maxVersion: Int = 0/*** The current snapshot version.*/private val currentVersion = AtomicInteger(0)/*** The list of all drawing snapshots.*/private val snapshots = ArrayList<AllDrawingsSnapshot>()/*** The default repository instance using local storage.*/private val defaultRepo = DefaultDrawingsSnapshotsRepo(getMaxVersion = ::maxVersion,setMaxVersion = ::maxVersion::set,getCurrentVersionCallback = currentVersion::get,incrementAndGetCurrentVersion = currentVersion::incrementAndGet,decrementAndGetCurrentVersion = currentVersion::decrementAndGet,snapshots = snapshots)/*** Method to add a new snapshot.** @param snapshot The snapshot to add.*/override fun addSnapshot(snapshot: AllDrawingsSnapshot) {defaultRepo.addSnapshot(snapshot)}/*** Checks if there is a previous step available.** @return True if a previous step is available, otherwise false.*/override fun hasPreviousStep(): Boolean {return defaultRepo.hasPreviousStep()}/*** Checks if there is a next step available.** @return True if a next step is available, otherwise false.*/override fun hasNextStep(): Boolean {return defaultRepo.hasNextStep()}/*** Checks if clearing is possible.** @return True if clearing is possible, otherwise false.*/override fun canClear(): Boolean {return defaultRepo.canClear()}/*** Moves to the previous step and returns the corresponding snapshot.** @return The previous snapshot, or null if not available.*/override fun previousStep(): AllDrawingsSnapshot? {return defaultRepo.previousStep()}/*** Moves to the next step and returns the corresponding snapshot.** @return The next snapshot, or null if not available.*/override fun nextStep(): AllDrawingsSnapshot? {return defaultRepo.nextStep()}/*** Retrieves the version of the current snapshot.** @return The version of the current snapshot.*/override fun currentVersion(): Int {return defaultRepo.currentVersion()}}